﻿using System;
using System.Collections.Generic;
using System.Net;
using AgentListener.Model.Database;
using AgentListener.Model.Network;
using AgentListener.Mongo;
using Common;
using Common.Configuration;
using Common.Annotations;
using MongoDB.Bson;

namespace AgentListener.Controllers.Strategies
{
    internal class RegisterStrategy : IRequestStrategy
    {
        private readonly IMongoProvider _mongoProvider;

        public RegisterStrategy([NotNull] IMongoProvider mongoProvider)
        {
            if (mongoProvider == null) throw new ArgumentNullException("mongoProvider");
            _mongoProvider = mongoProvider;
        }

        public ResponseInfo Process(RequestInfo data)
        {
            var syncData = JsonConvertWrapper.Deserialize<BaseData>(data.Query);

            if (syncData != null)
            {
                var agent = _mongoProvider.GetAgent(syncData.AgentId);

                if (agent != null && agent.Registered)
                    return new ResponseInfo(HttpStatusCode.InternalServerError, "ALREADY_REGISTERED");

                agent = CreateAgent(syncData);

                CreateAuth(agent);

                _mongoProvider.SaveAgent(agent);

                return new ResponseInfo(HttpStatusCode.OK, "REGISTRATION_SUCCESSFUL");
            }

            return new ResponseInfo(HttpStatusCode.InternalServerError, "Wrong json message format");
        }

        private void CreateAuth(Agent agent)
        {
            _mongoProvider.CreateAuth(agent.SysId, agent.AgentId);
        }

        private Agent CreateAgent(BaseData syncData)
        {
            //todo: вынести дефолты в отдельный конфиг??
            var agent = new Agent
                {
                    Id = ObjectId.GenerateNewId(),
                    SysId = syncData.SysId,
                    Registered = true,
                    Metrics = new List<Metric>
                        {
                            new Metric
                                {
                                    Name = "SysDiskSpc",
                                    Args = new List<string> {"/", "/usr"}
                                },
                            new Metric
                                {
                                    Name = "SysHostname",
                                    Args = new List<string>()
                                },
                            new Metric
                                {
                                    Name = "SysUptime",
                                    Args = new List<string>()
                                }
                        },
                    Location = new List<string> {"msk00.it-monitoring.com", "msk01.it-monitoring.com"},
                    Version = "0",
                    Status = AgentState.Up,
                    LastSyncDate = DateTime.Now
                };
            return agent;
        }
    }
}